namespace Study401 {

  type Person = {
    name: string;
    age: number;
    ispload: boolean;
  };


  type PersonKey = keyof Person   //// "name" | "age" | "ispload"


  interface Person2 {

    name: string;
    age: number;
    ispload: boolean;
  }

  type PersonKey2 = keyof Person2 // "name" | "age" | "ispload"


  // 类的属性名
  class Person3 {
    constructor(
      public name: string,
      public age: number,
      public isActive: boolean
    ) { }
  }
  // 获取类的属性名
  type PersonKey3 = keyof Person3  // "name" | "age" | "isActive"





  /**
   * 获取对象某个属性的值
   * @param obj 对象
   * @param key  对象的值
   * @returns 
   */
  function getProperty<O, K extends keyof O>(obj: O, key: K): O[K] {
    return obj[key];
  }

  let person = { name: "Alice", age: 30 };


  let student = { name: "Alice", age: 30, chengji: 333 };

  let p1 = getProperty(person, "age"); // 返回类型为 string

  let p2 = getProperty(person, "name"); // 返回类型为 string

  let p3 = getProperty(student, "chengji"); // 返回类型为 string


  // let invalid = getProperty(person, "height"); // 错误: "height" 不存在于 type "PersonKeys" 中




  type Config = {
    apiEndpoint: string;
    timeout: number;
  };


  // 使用示例
  let config: Config = {
    apiEndpoint: "https://api.example.com",
    timeout: 5000
  };

  // keyof Config  = "apiEndpoint" | "timeout"
  function updateConfig<T, K extends keyof T>(config: T, key: K, value: T[K]) {
    // key 必须是 Config 类型中的一个键
    // value 的类型必须与 Config[key] 的类型匹配
    // 更新 config 对象的属性
    config[key] = value;
    // updateConfig(config, "apiEndpoint", 233); // 合法
    // config["apiEndpoint"] = 233

  }


  updateConfig(config, "apiEndpoint", "sdff"); // 合法
  updateConfig<Config, keyof Config>(config, "apiEndpoint", "sdff"); // 合法
  // updateConfig(config, "apiEndpoint4", 444); // 合法

  // 1.控制 修改对象所传的键名范围 必须是对象的键名
  // 2.控制 所传对应键值的值类型 和 实际键对应的值的类型匹配


  console.log(config);



  //   遍历对象的属性
  // 可以使用 keyof 结合 in 关键字，来遍历对象类型的所有键。



  type Person4 = {
    name: string;
    age: number;
    isEmployed: boolean;
  };


  type Person4Kexuan = {
    [K in keyof Person4]?: Person4[K]
  }

  // for (const K in keyof Person4) {

  // }

  type Person4Kexuan3 = {
    name?: string | undefined;
    age?: number | undefined;
    isEmployed?: boolean | undefined;
  }


  type Person4Kexuan444 = {
    readonly [K in keyof Person4]: Person4[K]
  }


  const settings = {
    theme: "dark",
    version: "1.0",
    useCache: true,
  };

  // type settingsType = "theme" | "version" | "useCache"
  type settingsType = keyof typeof settings


}

export {}